//////////////////////////////////////////////////////////////////////////
#include "Button.h"
#include "Sprite/Sprite.h"
#include "HotSpot/HotSpot.h"
#include "Functor/Functor.h"
//////////////////////////////////////////////////////////////////////////
Button::Button()
: m_hotSpot(NULL)
, m_Pressed(false)
{

}
//////////////////////////////////////////////////////////////////////////
Button::~Button()
{
	m_Sprites.clear();

	if(m_ClickCb)
		delete m_ClickCb;
}
//////////////////////////////////////////////////////////////////////////
void Button::setSprites( const wchar_t* passive, const wchar_t* active /*= NULL*/, const wchar_t* press /*= NULL*/, const wchar_t* disable /*= NULL*/ )
{
	Sprite* sprite = new Sprite();
	sprite->setTexturePath(passive);
	addChild(sprite);
	m_Sprites[L"passive"] = sprite;

	if(active)
	{
		sprite = new Sprite();
		sprite->setTexturePath(active);
		addChild(sprite);
		m_Sprites[L"active"] = sprite;
	}

	if(press)
	{
		sprite = new Sprite();
		sprite->setTexturePath(press);
		addChild(sprite);
		m_Sprites[L"press"] = sprite;
	}

	if(disable)
	{
		sprite = new Sprite();
		sprite->setTexturePath(disable);
		addChild(sprite);
		m_Sprites[L"disable"] = sprite;
	}

	selectSprite(L"passive");

	setupHotSpot();
}
//////////////////////////////////////////////////////////////////////////
void Button::selectSprite( const wchar_t* name )
{
	for(std::map<std::wstring, Sprite*>::iterator it = m_Sprites.begin(); it != m_Sprites.end(); ++it)
	{
		(*it).second->setVisible(false);
	}

	m_Sprites[name]->setVisible(true);
}
//////////////////////////////////////////////////////////////////////////
bool Button::onMouseEvent( bool isDown )
{
	if(isDown)
	{
		selectSprite(L"press");		
	}
	else
	{
		selectSprite(L"active");
		if(m_Pressed && m_ClickCb)
			(*m_ClickCb)();
	}

	m_Pressed = isDown;

	return true;
}
//////////////////////////////////////////////////////////////////////////
bool Button::onMouseEnter()
{
	selectSprite(L"active");
	return true;
}
//////////////////////////////////////////////////////////////////////////
bool Button::onMoudeLeave()
{
	selectSprite(L"passive");
	m_Pressed = false;
	return true;
}
//////////////////////////////////////////////////////////////////////////
void Button::setupHotSpot()
{
	Sprite* sprite = m_Sprites[L"passive"];
	float width = static_cast<float>(sprite->getWidth());
	float height = static_cast<float>(sprite->getHeight());

	HotSpot* hotSpot = new HotSpot();
	hotSpot->addPoint(0, 0);
	hotSpot->addPoint(width, 0);
	hotSpot->addPoint(width, height);
	hotSpot->addPoint(0, height);
	hotSpot->setMouseEnterListener(createFunctor(this, &Button::onMouseEnter));
	hotSpot->setMouseLeaveListener(createFunctor(this, &Button::onMoudeLeave));
	hotSpot->setMouseEventListener(createFunctorArg(this, &Button::onMouseEvent));
	addChild(hotSpot);
	m_hotSpot = hotSpot;
}
//////////////////////////////////////////////////////////////////////////
void Button::setCenterAlign()
{
	assert(m_Sprites.size());
	if(!m_Sprites.size())
		return;

	for(std::map<std::wstring, Sprite*>::iterator it = m_Sprites.begin(); it != m_Sprites.end(); ++it)
	{
		(*it).second->setCenterAlign();
	}
	float width = static_cast<float>(m_Sprites[L"passive"]->getWidth());
	float height = static_cast<float>(m_Sprites[L"passive"]->getHeight());
	m_hotSpot->setXY(-width/2, -height/2);
}
//////////////////////////////////////////////////////////////////////////
